<template>

  <div class="container-print">
    <div class="upload-container-css">
      <div class="upload-section" id="upload-section-menu">
        <el-upload
            v-model:file-list="fileList"
            action="http://192.168.16.23:8443/print/uploadImg"
            list-type="picture-card"
            :show-file-list="false"
            :on-success="handleSuccess"
            :multiple="true"
            :limit="5"
            :disabled="displayImgUrl.length > 0"
        >
          <!-- 模板位置 -->
          <div class="template-class-position-display" :style="{ display: displayContent ? 'block' : 'none' }">
            <div class="template1-display" id="template1" style="border: 2px white solid">
              <!-- 使用 v-if 和 v-for 来根据条件生成 div 元素 -->
              <div v-if="displayImgUrl && displayImgUrl.length === 0">
                <!-- 如果 displayImgUrl 数组为空，生成三个固定的 div -->
                <div class="template1-children-display" v-for="n in 3" :key="n">

                </div>
              </div>
              <div v-else>
                <!-- 如果 displayImgUrl 数组不为空，正常遍历显示图片 -->
                <div class="template1-children-display" v-for="(imgData, index) in displayImgUrl" :key="index">
                  <el-icon @click="removeCurImg(imgData.url, $event)" class="close-icon">
                    <Close class="el-icon-close"/>
                  </el-icon>

                  <div class="zoom-container" ref="scrollContainer"
                       @touchstart="onTouchStart($event, index)"
                       @touchmove="onTouchMove($event, index)"
                       @touchend="onTouchEnd"
                  >
                    <el-image :class="'zoomable-image' + index"
                              :ref="'zoomImg' + index"
                              @wheel="handleZoom($event, index)"
                              crossorigin="anonymous"
                              :style="{ transform: `scale(${imgData.scale}) translate(${imgData.translateX}px, ${imgData.translateY}px) rotate(${imgData.rotation}deg)` }"
                              :src="imgData.url" alt=""/>
                  </div>
                </div>
              </div>
            </div>
          </div>

          <!-- Canvas 元素用于合成图片 -->
          <div class="add-image-source">
            <span class="icon-style-class" :style="{ display: isTemplateVisible ? 'block' : 'none' }">
            <el-icon class="add-resource">
              <Plus/>
            </el-icon>
            </span>
            <span class="add-image" :style="{ display: isTemplateVisible ? 'block' : 'none' }">添加照片</span>
          </div>
        </el-upload>
      </div>
      <div class="image-list-section">
        <div class="small-image">
          <ul class="small">
            <li v-for="(url, index) in imageUrlList" :key="index"
                @click="handleMoveImage(url, index)"
                @touchstart="startLongPressTimer(url, index)"
                @touchend="cancelLongPressTimer">
              <el-image crossorigin="anonymous" style="width: 80px;height: 83px" :src="url" alt=""/>
            </li>
          </ul>
        </div>
      </div>
    </div>
    <div class="dialog-class-style">
      <el-dialog v-model="dialogVisible">
        <img class="display-large-img" :src="dialogImageUrl" alt="Preview Image"/>
      </el-dialog>
    </div>

    <iframe id="iframe" name="iframeName" style="display: none"></iframe>
    <!-- 模板位置 -->
    <div class="template-class-position">
      <div class="template1" id="template1" style="border: 2px white solid" :class="{ 'selected': isSelectedTemplate1 }"
           @click="selectTemplate1()">
        <div class="template1-children"></div>
        <div class="template1-children"></div>
        <div class="template1-children"></div>
      </div>
      <div class="template2" id="template2" style="border: 1px white solid" :class="{ 'selected': isSelectedTemplate2 }"
           @click="selectTemplate2()">
        <div class="template2-children"></div>
        <div class="template2-grid">
          <div class="template2-children-grip"></div>
          <div class="template2-children-grip"></div>
        </div>
      </div>
    </div>

    <div class="print-option">
      <span>
        <el-upload class="keep-trying-upload"
                   v-model:file-list="fileList"
                   action="http://192.168.16.23:8443/print/uploadImg"
                   :show-file-list="false"
                   :on-success="handleSuccess"
                   :multiple="true"
                   :limit="5"
        >
          <el-button color="white" class="keep-trying-upload">
          <el-icon class="add-icon-class">
        <Plus/>
      </el-icon>继续上传({{ this.fileList.length }}/5)</el-button></el-upload>
      </span>
      <span>
        <el-button color="yellow" class="right-now-print" @click="synthesisImg()">立即打印</el-button>
      </span>
    </div>
  </div>
  <canvas id="myCanvas" width="595" height="842"></canvas>
</template>

<script>

// import * as medicalStyle from '@/assets/style/eye/medical/standard.css'
// import print from 'print-js'
import axios from 'axios'
import {ElMessage} from 'element-plus';
import {Plus, Close} from '@element-plus/icons-vue'
import '../assets/style/print.css'


export default {
  data() {
    return {
      fileList: [],
      imageUrlList: [], // 存放上传成功后的图片地址
      dialogVisible: false,
      dialogImageUrl: '',
      isSelectedTemplate1: false,
      isSelectedTemplate2: false,
      draggedImageUrl: null,
      displayContent: false,
      isTemplateVisible: true,
      displayImgUrl: [],
      scaleFactor: 0.5,  // 缩放比例因子
      longPressDuration: 500, // 长按持续时间，单位毫秒
    };
  },
  components: {Plus, Close},
  methods: {
    handleSuccess(response, file, fileList) {

      console.log("图片资源", this.fileList)
      console.log(response)
      // 上传成功的回调函数
      this.fileList = fileList; // 更新文件列表
      // 假设 response 包含多张图片的地址，例如一个数组或逗号分隔的字符串
      // 这里只是示例，具体取决于后端返回的数据结构
      let url = response; // 假设返回的是一个包含图片地址的数组
      let reallyUrl = 'http://192.168.16.23:8443/api/file/' + url;
      console.log(reallyUrl)
      this.imageUrlList.push(reallyUrl)

      // 上传图片成功啦 将图标和文题隐藏

    },
    printDivContent() {
      const formData = new FormData();
      // const fileInput = document.getElementById('fileInput');
      // formData.append("file", this.fileList[0]);
      console.log("文件列表", this.fileList)

      for (let file of this.fileList) {
        formData.append('files', file.raw);
      }
      console.log("传递的文件参数:", formData)
      axios.post('http://192.168.16.23:8443/print/printImg', formData).then(function (res) {
        if (res.data.code === 200) {
          console.log("返回的数据", res.data.data)
          ElMessage.success(res.data.msg)
        } else {
          ElMessage.error(res.data.msg)
        }
      })
    },
    selectTemplate1() {
      if (this.fileList.length == 0) {
        return ElMessage.error("当前未上传图片，不能选择模板")
      }
      this.isSelectedTemplate2 = false
      // 显示图片布局
      this.displayContent = true;
      this.isTemplateVisible = false

      alert("选择了模板一")
    },
    selectTemplate2() {
      this.isSelectedTemplate1 = false
      this.isSelectedTemplate2 = true
      // 点击是将上传的位置切换成这个
      const template1 = document.getElementById('template2').innerHTML;
      document.getElementById('upload-section-menu').innerHTML = template1;
      alert("选择了模板二")
    },
    handleMoveImage(url, index) {

      // 显示图片布局
      this.displayContent = true;

      // 初始化 displayImgUrl 为一个空数组，如果没有初始化过的话
      if (!this.displayImgUrl) {
        this.displayImgUrl = [];
      }

      // 判断 url 是否已经在 displayImgUrl 中
      let existingImage = this.displayImgUrl.find(image => image.url === url);
      if (!existingImage) {
        // 如果不存在，则初始化图片对象并添加到数组中
        let newImage = this.createImageObject(url);
        this.displayImgUrl.push(newImage);
      }

      // 如果 displayImgUrl 不为 null 或 undefined，并且有内容，设置 isTemplateVisible 为 false
      if (this.displayImgUrl.length > 0) {
        this.isTemplateVisible = false;
      }

      console.log("图片对象列表", this.displayImgUrl);
      console.log(index);
    },
    // 定义图片对象的格式
    createImageObject(url) {
      return {
        url: url,
        scale: 1,
        translateX: 0,
        translateY: 0,
        touchStartX: 0,
        touchStartY: 0,
        initialpinchDistance: 0,
        rotation: 0,
        initialAngle: 0
      };
    },
    // 当点击时删除
    removeCurImg(url, event) {
      event.stopPropagation();
      // 找到 url 在 displayImgUrl 中的索引
      const index = this.displayImgUrl.findIndex(img => img.url === url);
      if (index !== -1) {
        // 如果找到了，从数组中删除该元素
        this.displayImgUrl.splice(index, 1);
      }
    },
    async synthesisImg() {
      const displayImgUrl = this.displayImgUrl; // 假设这是你的图片数据数组
      const canvas = document.getElementById('myCanvas');
      const ctx = canvas.getContext('2d');

      // 计算最大宽度和高度
      let maxWidth = 0;
      let totalHeight = 0;
      const borderWidth = 5;
      const padding = 20; // 添加间距
      // const borderColor = 'rgba(0,0,0,0.22)';

      // 预加载所有图片获取实际尺寸和缩放比例
      const images = await Promise.all(displayImgUrl.map(imgData => {
        return new Promise((resolve, reject) => {
          const img = new Image();
          img.crossOrigin = 'anonymous';
          img.onload = function () {
            imgData.width = img.naturalWidth;
            imgData.height = img.naturalHeight;
            resolve(img);
          };
          img.onerror = function (err) {
            reject(err);
          };
          img.src = imgData.url;
        });
      }));

      // 根据图片尺寸和缩放比例来计算 Canvas 大小
      images.forEach((img, index) => {
        const imgData = displayImgUrl[index];
        imgData.scale = imgData.scale || 1;
        imgData.rotation = imgData.rotation || 0;

        // 计算旋转后的宽高
        const rotatedWidth = Math.abs(imgData.width * Math.cos(imgData.rotation * Math.PI / 180)) +
            Math.abs(imgData.height * Math.sin(imgData.rotation * Math.PI / 180));
        const rotatedHeight = Math.abs(imgData.width * Math.sin(imgData.rotation * Math.PI / 180)) +
            Math.abs(imgData.height * Math.cos(imgData.rotation * Math.PI / 180));

        const scaledWidth = rotatedWidth * imgData.scale;
        const scaledHeight = rotatedHeight * imgData.scale;

        if (scaledWidth > maxWidth) {
          maxWidth = scaledWidth;
        }
        totalHeight += scaledHeight + padding;
      });

      // 设置 Canvas 的宽高
      canvas.width = Math.ceil(maxWidth);
      canvas.height = Math.ceil(totalHeight);

      // 清空 Canvas
      ctx.clearRect(0, 0, canvas.width, canvas.height);

      let y = 0;

      // 绘制图片和边框
      images.forEach((img, index) => {
        const imgData = displayImgUrl[index];
        const scale = imgData.scale || 1;
        const rotation = imgData.rotation || 0;
        // const scaledWidth = imgData.width * scale;
        // const scaledHeight = imgData.height * scale;

        // 计算旋转后的实际边界框
        const rotatedWidth = Math.abs(imgData.width * Math.cos(rotation * Math.PI / 180)) +
            Math.abs(imgData.height * Math.sin(rotation * Math.PI / 180));
        const rotatedHeight = Math.abs(imgData.width * Math.sin(rotation * Math.PI / 180)) +
            Math.abs(imgData.height * Math.cos(rotation * Math.PI / 180));

        const rotatedScaledWidth = rotatedWidth * scale;
        const rotatedScaledHeight = rotatedHeight * scale;

        ctx.setTransform(1, 0, 0, 1, 0, 0); // 重置当前的变换矩阵
        ctx.save();
        ctx.translate(rotatedScaledWidth / 2, y + rotatedScaledHeight / 2);
        ctx.rotate(rotation * Math.PI / 180);
        ctx.scale(scale, scale);

        ctx.imageSmoothingEnabled = true;
        ctx.drawImage(img, -imgData.width / 2, -imgData.height / 2, imgData.width, imgData.height);
        ctx.restore();

        y += (rotatedScaledHeight + padding);
      });

      // 使用 requestAnimationFrame 来确保 Canvas 准备好后再生成 Blob
      requestAnimationFrame(() => {
        canvas.toBlob(function (blob) {
          if (!blob) {
            ElMessage.error('当前图片过大，请进行适量收缩');
            return;
          }

          const formData = new FormData();
          formData.append("files", blob);

          axios.post('http://192.168.16.23:8443/print/printImg', formData).then(function (res) {
            if (res.data.code === 200) {
              console.log("返回的数据", res.data.data);
              ElMessage.success(res.data.msg);
            } else {
              ElMessage.error(res.data.msg);
            }
          }).catch(function (err) {
            console.error('上传出错', err);
          });
        });
      });
    },
    handleZoom(event, index) {
      event.preventDefault();
      this.$nextTick(() => {
        const zoomImg = document.querySelector('.zoomable-image' + index);
        if (!zoomImg) return; // 确保 $refs 引用存在

        const container = zoomImg.parentElement;
        if (!container) return;

        const containerWidth = container.clientWidth;
        const containerHeight = container.clientHeight;

        let newWidth, newHeight;

        const deltaY = event.deltaY;
        if (deltaY > 0) {
          // 缩小
          newWidth = zoomImg.offsetWidth / this.scaleFactor;
          newHeight = zoomImg.offsetHeight / this.scaleFactor;
        } else {
          // 放大
          newWidth = zoomImg.offsetWidth * this.scaleFactor;
          newHeight = zoomImg.offsetHeight * this.scaleFactor;
        }
        // 检查是否超出容器尺寸，如果超出，则限制到容器边界
        if (newWidth <= containerWidth && newHeight <= containerHeight) {
          zoomImg.style.width = `${newWidth}px`;
          zoomImg.style.height = `${newHeight}px`;
        } else {
          // 如果超出容器尺寸，限制到容器边界
          zoomImg.style.width = `${containerWidth}px`;
          zoomImg.style.height = `${containerHeight}px`;
        }

      });
    },
    onTouchStart(event, index) {
      if (event.touches.length === 2) {
        // 计算初始触摸点之间的距离
        this.displayImgUrl[index].initialpinchDistance = Math.hypot(
            event.touches[0].clientX - event.touches[1].clientX,
            event.touches[0].clientY - event.touches[1].clientY
        );
      } else {
        // 记录单点触摸的起始位置
        this.touchStartX = event.touches[0].clientX;
        this.touchStartY = event.touches[0].clientY;
      }
    },
    onTouchMove(event, index) {
      event.preventDefault();

      if (event.touches.length === 2) {
        // 双指缩放
        const touch1 = event.touches[0];
        const touch2 = event.touches[1];

        // 计算当前距离和角度
        const currentDistance = Math.hypot(touch2.clientX - touch1.clientX, touch2.clientY - touch1.clientY);
        // 计算旋转角度
        const deltaX = touch2.clientX - touch1.clientX;
        const deltaY = touch2.clientY - touch1.clientY;
        const currentAngle = Math.atan2(deltaY, deltaX) * (180 / Math.PI); // 0.5 是一个调整系数，可以根据需要调整


        if (!this.displayImgUrl[index].initialpinchDistance) {
          // 如果初始距离未设置，设置初始距离和角度
          this.displayImgUrl[index].initialpinchDistance = currentDistance;
          this.displayImgUrl[index].initialAngle = currentAngle;
        }

        // 计算缩放比例和旋转角度变化
        const scaleRatio = currentDistance / this.displayImgUrl[index].initialpinchDistance;
        const angleDelta = currentAngle - this.displayImgUrl[index].initialAngle;

        // 更新初始距离和角度
        this.displayImgUrl[index].initialpinchDistance = currentDistance;
        this.displayImgUrl[index].initialAngle = currentAngle;

        // 应用缩放和旋转
        requestAnimationFrame(() => {
          this.displayImgUrl[index].scale *= scaleRatio;
          this.displayImgUrl[index].rotation += angleDelta;
        });

      } else if (event.touches.length === 1) {
        // 计算移动
        const touchX = event.touches[0].clientX;
        const touchY = event.touches[0].clientY;
        const deltaX = touchX - this.touchStartX;
        const deltaY = touchY - this.touchStartY;


        // 使用 requestAnimationFrame 平滑移动
        requestAnimationFrame(() => {
          this.displayImgUrl[index].translateX += deltaX;
          this.displayImgUrl[index].translateY += deltaY;
        });

        this.touchStartX = touchX;
        this.touchStartY = touchY;
      }
    },
    onTouchEnd() {
      // 清理工作（如果需要）
    },

    startLongPressTimer(url, index) {
      this.longPressTimer = setTimeout(() => {
        this.deleteImage(index, url);
      }, this.longPressDuration);
    },
    cancelLongPressTimer() {
      clearTimeout(this.longPressTimer);
    },
    deleteImage(index, url) {
      // 弹出确认框
      if (window.confirm('确定要删除这张图片吗？')) {
        // 用户点击了确认按钮，执行删除操作
        this.imageUrlList.splice(index, 1);
        // 找到 displayImgUrl 中对应的路径并删除
        const displayIndex = this.displayImgUrl.findIndex(item => item.url === url);
        if (displayIndex !== -1) {
          this.displayImgUrl.splice(displayIndex, 1);
        }
      } else {
        // 用户点击了取消按钮，取消删除操作
        console.log('取消删除');
      }
    }
  }
};
</script>

<style>
#app {
  font-family: Avenir, Helvetica, Arial, sans-serif;
  -webkit-font-smoothing: antialiased;
  -moz-osx-font-smoothing: grayscale;
  text-align: center;
  color: #2c3e50;
  margin: 0;
}

.img-upload {
  margin-bottom: 20px;
}


</style>
